<?xml version="1.0" encoding="UTF-8"?>

<xs:schema id="schema.a42"
    xmlns:xs="http://www.w3.org/2001/XMLSchema"
    targetNamespace="http://a42.vodafone.com/versions/a42/v1"
    xmlns:a42ns="http://a42.vodafone.com/versions/a42/v1"
    elementFormDefault="qualified"
    >
    
    <xs:defaultOpenContent mode="interleave">
        <xs:any namespace="##any" processContents="lax" />
    </xs:defaultOpenContent>
    
    <!-- +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ -->
    <!-- Definition of XML representations for common A42 resources and related DTOs. -->
    <!-- +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ -->
    
    <!-- A generic (key, value) pair. -->
    <xs:complexType name="KeyValueType">
        <xs:attribute name="key" type="xs:string" use="required" />
        <xs:attribute name="value" type="xs:string" use="optional" />
    </xs:complexType>
    
    <!-- A collection of (key, value) pairs that can be used to provide arbitrary details for whatever. -->
    <xs:complexType name="KeyValueCollectionType">
        <xs:all>
            <xs:element name="keyValue" type="a42ns:KeyValueType" minOccurs="0" maxOccurs="unbounded" />
        </xs:all>
    </xs:complexType>
    
    <!-- All kinds of generic link types. -->
    <xs:complexType name="LinkType">
        <xs:attribute name="rel" type="xs:string" use="optional" />
        <xs:attribute name="href" type="xs:anyURI" use="required" />
        <xs:attribute name="method" type="xs:string" use="optional" />
        <xs:attribute name="hreflang" type="xs:string" use="optional" />
        <xs:attribute name="media" type="xs:string" use="optional" />
        <xs:attribute name="type" type="xs:string" use="optional" />
        <xs:attribute name="sizes" type="xs:string" use="optional" />
    </xs:complexType>

    <xs:simpleType name="identityAndRenderingLinkRelationType">
        <xs:restriction base="xs:string">
            <xs:enumeration value="self" />
            <xs:enumeration value="http://a42.vodafone.com/rels/a42/rendering/default" />
            <xs:enumeration value="http://a42.vodafone.com/rels/a42/rendering/imploded" />
            <xs:enumeration value="http://a42.vodafone.com/rels/a42/rendering/exploded" />
        </xs:restriction>
    </xs:simpleType>
    <xs:simpleType name="paginationLinkRelationType">
        <xs:restriction base="xs:string">
            <xs:enumeration value="first" />
            <xs:enumeration value="last" />
            <xs:enumeration value="previous" />
            <xs:enumeration value="next" />
        </xs:restriction>
    </xs:simpleType>
    
    <!-- "self" is an IANA-defined link relation name. -->
    <xs:complexType name="SelfLinkType">
        <xs:complexContent>
            <xs:restriction base="a42ns:LinkType">
                <xs:attribute name="rel" type="xs:string" use="required" fixed="self" />
            </xs:restriction>
        </xs:complexContent>
    </xs:complexType>
    <!-- "help" is an IANA-defined link relation name. -->
    <xs:complexType name="HelpLinkType">
        <xs:complexContent>
            <xs:restriction base="a42ns:LinkType">
                <xs:attribute name="rel" type="xs:string" use="required" fixed="help" />
            </xs:restriction>
        </xs:complexContent>
    </xs:complexType>
    <!-- Link relation type for a service document. -->
    <xs:complexType name="ServiceDocumentLinkType">
        <xs:complexContent>
            <xs:restriction base="a42ns:LinkType">
                <xs:attribute name="rel" type="xs:string" use="required"
                    fixed="http://a42.vodafone.com/rels/a42/serviceDocument" />
            </xs:restriction>
        </xs:complexContent>
    </xs:complexType>
    <!-- Link relation type for a service document. -->
    <xs:complexType name="TaskSourceLinkType">
        <xs:complexContent>
            <xs:restriction base="a42ns:LinkType">
                <xs:attribute name="rel" type="xs:string" use="required"
                    fixed="http://a42.vodafone.com/rels/a42/tasking/source" />
            </xs:restriction>
        </xs:complexContent>
    </xs:complexType>
    
    <!-- +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ -->
    
    <!-- Possible values for the "rendering" attribute in resources. -->
    <xs:simpleType name="ResourceRenderingType">
        <xs:restriction base="xs:string">
            <xs:enumeration value="default"/>
            <xs:enumeration value="condensed"/>
            <xs:enumeration value="exploded"/>
        </xs:restriction>
    </xs:simpleType>

    <xs:complexType name="ResourceMetaType">
        <xs:all>
            <xs:element name="links" type="a42ns:LinkArrayType" minOccurs="1" maxOccurs="1"/>
        </xs:all>
        <!-- The internal ID of this resource. -->
        <xs:attribute name="id" type="xs:string" use="optional" />
        <!-- Complete ID of this resource as URN. -->
        <xs:attribute name="urn" type="xs:string" use="optional" />
        <!-- Timestamp of the creation of this resource. -->
        <xs:attribute name="createdAt" type="xs:dateTime" use="optional" />
        <!-- Timestamp of the last update of this resource. -->
        <xs:attribute name="updatedAt" type="xs:dateTime" use="optional" />
        <!-- Gives a hint if the representation is condensed or exploded. -->
        <xs:attribute name="rendering" type="a42ns:ResourceRenderingType" use="optional" />
    </xs:complexType>

    <xs:complexType name="LinkArrayType">
        <xs:all>
            <xs:element name="link" type="a42ns:LinkType" minOccurs="1" maxOccurs="unbounded"/>
        </xs:all>
    </xs:complexType>
    
    <!-- Basic type for resource representations. -->
    <xs:complexType abstract="true" name="ResourceType">
        <xs:all>
            <xs:element name="resourceMeta" type="a42ns:ResourceMetaType" minOccurs="0" maxOccurs="1"/>
        </xs:all>
    </xs:complexType>
    
    <xs:complexType name="ResourcePaginationType">
        <xs:all>
            <xs:element name="links" type="a42ns:LinkArrayType" minOccurs="1" maxOccurs="1"/>
        </xs:all>
        <xs:attribute name="itemsOnPage" type="xs:int" use="optional" />
        <xs:attribute name="totalItems" type="xs:long" use="optional" />
        <xs:attribute name="currentPageNum" type="xs:int" use="optional" />
        <xs:attribute name="firstPageNum" type="xs:int" use="optional" />
        <xs:attribute name="lastPageNum" type="xs:int" use="optional" />
        <xs:attribute name="totalPages" type="xs:int" use="optional" />
    </xs:complexType>
    
    <xs:complexType abstract="true" name="PaginatableResourceType">
        <xs:complexContent>
            <xs:extension base="a42ns:ResourceType">
                <xs:all>
                    <xs:element name="resourcePagination" type="a42ns:ResourcePaginationType" minOccurs="0" maxOccurs="1"/>
                </xs:all>
            </xs:extension>
        </xs:complexContent>
    </xs:complexType>
    
    <!-- +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ -->
    
    <!-- Container for error messages and descriptions. It's possible, but not necessary to implement this as a resource. In either case, an
        implementation should populate the "id" attribute to provide a correlation between the error representation and a log file. -->
    <xs:element name="error">
        <xs:complexType>
            <xs:complexContent>
                <xs:extension base="a42ns:ResourceType">
                    <xs:all>
                        <!-- A brief message describing the error condition. -->
                        <xs:element name="message" type="xs:string" minOccurs="1" maxOccurs="1" />
                        <!-- A longer description with information on how to fix the error condition, if applicable. -->
                        <xs:element name="description" type="xs:string" minOccurs="1" maxOccurs="1" />
                        <!-- Even more details as a collection of (key, value) pairs. -->
                        <xs:element name="details" type="a42ns:KeyValueCollectionType" minOccurs="0" maxOccurs="1" />
                        <!-- Can contain a link that can provide help on solving the issue, e.g. documentation and the like. -->
                        <!-- That would be link relation type "help". -->
                        <xs:element name="links" type="a42ns:LinkArrayType" minOccurs="1" maxOccurs="1"/>
                    </xs:all>
                </xs:extension>
            </xs:complexContent>
        </xs:complexType>
    </xs:element>
    
    <xs:element name="task" type="a42ns:TaskType" />
    <xs:complexType name="TaskType">
        <xs:complexContent>
            <xs:extension base="a42ns:ResourceType">
                <xs:all>
                    <xs:element name="type" type="xs:string" minOccurs="0" maxOccurs="1" />
                    <xs:element name="status" type="xs:string" minOccurs="0" maxOccurs="1" />
                    <xs:element name="message" type="xs:string" minOccurs="0" maxOccurs="1" />
                    <xs:element name="progress" type="xs:unsignedByte" minOccurs="0" maxOccurs="1" />
                    <xs:element name="pingAfter" type="xs:dateTime" minOccurs="0" maxOccurs="1" />
                    <xs:element name="expiresAt" type="xs:dateTime" minOccurs="0" maxOccurs="1" />
                    <xs:element name="completedAt" type="xs:dateTime" minOccurs="0" maxOccurs="1" />
                    <xs:element name="source" minOccurs="0" maxOccurs="1">
                        <xs:complexType>
                            <xs:choice>
                                <xs:element name="link" type="a42ns:TaskSourceLinkType"/>
                                <xs:any namespace="##any" processContents="lax" />
                            </xs:choice>
                        </xs:complexType>
                    </xs:element>
                </xs:all>
            </xs:extension>
        </xs:complexContent>
    </xs:complexType>
    
    <!-- +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ -->
    
</xs:schema>
